<template>
	<view class="calendar-wrap">
		<view class="header">
			<view class="left-wrap">
				<view class="cur-date" @click="selectDate">{{ curDate }}</view>
				<view class="back-to-today" @click="backToToday">回到今天</view>
			</view>
			<view class="more-btn" @click="onViewMore">
				<text class="btn-text">查看打卡记录</text>
				<u-icon name="arrow-right" color="#919191" size="15" />
			</view>
		</view>
		<view class="calendar-container">
			<view class="week-row">
				<view v-for="item in weekName" :key="item" class="week">{{ item }}</view>
			</view>

			<!-- 收起：展示当天日期所在周日期数据 -->
			<view v-if="!isExpend" class="date-wrap" :style="{height: '80rpx'}">
				<block v-if="isCurMonth">
					<view v-for="(item, index) in curWeekDates" :key="index" class="date-item"
						@click="onDateClick(item)">
						<view v-if="item" class="date-value" :class="{
                'date-value_active': activeDate === item.date,
                'date-value_clockin': item && item.clockedType === 'clockin',
                'date-value_reclockin': item && item.clockedType === 'reclockin',
              }">
							{{ item ? item.day : '' }}
						</view>
						<!-- 展示条件：1、有日期信息 2、当前日期有打卡记录 -->
						<view v-if="item && item.clockedType === 'clockin'" class="clockin-tag" />
						<view v-if="item && item.clockedType === 'reclockin'" class="clockin-tag reclockin-tag" />
					</view>
				</block>
				<block v-else>
					<view v-for="(item, index) in allDates" :key="index" class="date-item" @click="onDateClick(item)">
						<view class="date-value" :class="{
                'date-value_active': activeDate === item.date,
                'date-value_clockin': item && item.clockedType === 'clockin',
                'date-value_reclockin': item && item.clockedType === 'reclockin',
              }">
							{{ item ? item.day : '' }}
						</view>
						<!-- 展示条件：1、有日期信息 2、当前日期有打卡记录 -->
						<view v-if="item && item.clockedType === 'clockin'" class="clockin-tag" />
						<view v-if="item && item.clockedType === 'reclockin'" class="clockin-tag reclockin-tag" />
					</view>
				</block>
			</view>

			<!-- 展开：展示所有日期 -->
			<view v-else class="date-wrap">
				<view v-for="(item, index) in allDates" :key="index" class="date-item" @click="onDateClick(item)">
					<view class="date-value" :class="{
              'date-value_active': activeDate === item.date,
              'date-value_clockin': item && item.clockedType === 'clockin',
              'date-value_reclockin': item && item.clockedType === 'reclockin',
            }">
						{{ item ? item.day : '' }}
					</view>
					<!-- 展示条件：1、有日期信息 2、当前日期有打卡记录且补卡次数为0 -->
					<view v-if="item && item.clockedType === 'clockin'" class="clockin-tag" />
					<view v-if="item && item.clockedType === 'reclockin'" class="clockin-tag reclockin-tag" />
				</view>
			</view>
			<view class="expend-btn" @click="onExpend">
				<view class="line" />
				<u-icon color="#7e7e7e" :name="isExpend ? 'arrow-up' : 'arrow-down'" class="expend-icon" />
				<view class="line" />
			</view>

			<view class="clock-in-btn-wrap">
				<view v-if="clockInBtnShow" class="btn" :class="{'btn-disabled': clockInBtnDisabled }"
					@click="onToClockIn">
					{{ clockInBtnText || '打卡' }}
				</view>
				<view v-if="clockInInfoShow" class="info-wrap">
					<view class="count">今日已打卡<text>{{ curActiveDateInfo.day_num }}</text>/{{ clockInRuleData.max_num }}次
					</view>
					<view class="coin-getted-count">
						<text>已领{{ curActiveDateInfo.points }}青币</text>
						<image src="../../../../static/images/points/coin_16x16.png" style="width: 16px;height:16px;" />
					</view>
				</view>
			</view>
		</view>

		<u-datetime-picker ref="datePickerRef" v-model="datePickerValue" :show="datetimePickShow" mode="year-month"
			close-on-click-overlay confirm-color="#78ffe6" @cancel="onDatetimePickerCancel"
			@confirm="onDatetimePickerConfirm" />

		<!-- 无补卡机会提示用户去浏览手账 -->
		<u-modal :show="modalConfig.show" :title="modalConfig.title" :content="modalConfig.content"
			@confirm="onModalConfirm" />
	</view>
</template>

<script>
	import {
		mapState
	} from 'vuex'
	import dayJs from 'dayjs'
	import isSameOrBefore from 'dayjs/plugin/isSameOrBefore'
	dayJs.extend(isSameOrBefore)

	import {
		wx_clockin_log_list,
		wx_template_subscribe
	} from '../../../../api/index.js'
	import config from '@/config.js'
	import {
		getCurrentTemplateSubscribe
	} from '@/utils'
	export default {
		name: 'Calendar',
		data() {
			return {
				datePickerValue: dayJs().valueOf(),
				curDate: dayJs().format('YYYY-MM'),
				allDates: [],
				weekName: ['日', '一', '二', '三', '四', '五', '六'],
				activeDate: dayJs().format('YYYY-MM-DD'),
				curActiveDateInfo: {
					day_num: 0,
					points: 0,
					reclock_num: 0
				},
				isExpend: false,
				datetimePickShow: false,
				curWeekDates: [], // 当前周日期数据
				isCurMonth: true,
				modalConfig: {
					show: false,
					title: '温馨提示',
					content: '您当前无补卡机会，去逛青丝手账得补卡机会吧！'
				}
			}
		},
		computed: {
			...mapState(['clockInDetail', 'clockInRuleData']),
			clockInBtnDisabled() {
				if (dayJs(this.curDate).month() + 1 < dayJs().month() + 1) return true
				// console.log('---打卡按钮禁用---')
				// console.log(this.curActiveDateInfo)
				// console.log('打卡规则')
				// console.log(this.clockInRuleData)
				const {
					isToday,
					day_num
				} = this.curActiveDateInfo
				// let makeCount = 0 // 补卡次数
				// if (this.clockInDetail.clockin_data) {
				//   makeCount = this.clockInDetail.clockin_data.left_num
				// }
				// 当天打卡次数用完，则打卡按钮禁用置灰
				if (isToday && day_num === this.clockInRuleData.max_num) {
					return true
				}
				return false
			},
			clockInInfoShow() {
				const {
					date
				} = this.curActiveDateInfo
				const curDate = dayJs().format('YYYY-MM-DD')
				return date > curDate ? false : true
			},
			clockInBtnShow() {
				if (dayJs(this.curDate).month() + 1 < dayJs().month() + 1) return false
				const {
					isToday,
					month,
					date,
					day_num,
					reclock_num
				} = this.curActiveDateInfo

				// console.log('打卡规则')
				// console.log(this.clockInRuleData)
				const curDate = dayJs().format('YYYY-MM-DD')
				if (isToday) return true
				// 如果选择的是当天之后的日期，则不显示打卡按钮和打卡次数信息区域
				if (date > curDate) {
					return false
				}

				// 如果选择当天之前的日期，如果那一天打过卡 或者 补卡次数全部用完，则按钮不展示
				if (date < curDate) {
					// 如果之前日期没有打过卡 或者已补卡次数未超过最大补卡次数，则显示按钮
					if (day_num === 0 || (reclock_num !== 0 && reclock_num < this.clockInRuleData.max_renum)) return true

					// 之前日期补卡次数用完，不展示按钮
					if (reclock_num === this.clockInRuleData.max_renum) return false

					// 打过卡未补卡时，不展示按钮
					if (day_num && reclock_num === 0) return false
				}

				// 如果选择的是上个月的日期，则不显示按钮
				if (month < dayJs().month() + 1) {
					return false
				}
			},
			clockInBtnText() {
				if (dayJs(this.curDate).month() + 1 < dayJs().month() + 1) return
				const {
					isToday,
					date,
					day_num,
					reclock_num
				} = this.curActiveDateInfo
				const curDate = dayJs().format('YYYY-MM-DD')
				if (date < curDate) {
					// 选择的是当天之前的日期并且那天未打过卡，则按钮内容为：补卡
					// && (day_num === 0 || (reclock_num !== 0 && reclock_num < this.clockInRuleData.max_renum))
					if (day_num === 0 || (reclock_num !== 0 && reclock_num < this.clockInRuleData.max_renum)) {
						return '补卡'
					}
				}
				if (isToday) {
					return '打卡'
				}
			}
		},
		watch: {
			clockInDetail() {
				const year = dayJs(this.curDate).year()
				const month = dayJs(this.curDate).month() + 1
				this.initCalendar(year, month)
			}
		},
		mounted() {
			this.$emit('date:update', this.curDate)
		},
		methods: {
			async initCalendar(year = dayJs().year(), month = dayJs().month() + 1) {
				const startOfMonth = dayJs(new Date(year, month - 1, 1))
				const endOfMonth = dayJs(new Date(year, month, 0))
				let dates = []
				let current = startOfMonth

				while (current.isSameOrBefore(endOfMonth)) {
					let dateData = {
						year: current.year(),
						month: current.month() + 1,
						day: current.date(), // 当天日期
						week: current.day(), // 周几 0-6
						date: current.format('YYYY-MM-DD'),
						isToday: current.isSame(dayJs(), 'day'),
						timestamp: current.toDate().getTime(),
						clockedType: '', // 是否打过卡
						day_num: 0, // 已打卡次数
						reclock_num: 0, // 已补卡次数
						points: 0 // 当天领的青币数
					}
					// 判断该日期是已打卡，如果参与过打卡，将打卡信息添加进去
					// console.log('打卡详情')
					// console.log(this.clockInDetail)
					if (this.clockInDetail) {
						const {
							clockin_days
						} = this.clockInDetail
						if (clockin_days.length) {
							const existData = clockin_days.find(e => e.create_date === dateData.date)
							if (existData) {
								const {
									day_num,
									points,
									reclock_num
								} = existData
								dateData.day_num = day_num
								dateData.points = points
								dateData.reclock_num = reclock_num
								dateData.clockedType = reclock_num === 0 && day_num ? 'clockin' : 'reclockin'
							}
						}
					}
					dates.push(dateData)
					current = current.add(1, 'day')
				}

				const fetchData = dates.find(e => e.date === this.activeDate)
				this.curActiveDateInfo = fetchData || dates.filter(e => e !== undefined)[0]
				// this.curActiveDateInfo.day_num = fetchData ? fetchData.day_num : 0
				// this.curActiveDateInfo.points = fetchData ? fetchData.points : 0
				let empty = [...Array(dates[0].week)]
				dates = empty.concat(dates)
				const suffixDiff = 35 - dates.length
				if (suffixDiff > 0) {
					dates = dates.concat([...Array(suffixDiff)])
				}
				this.allDates = dates

				console.log('添加过打卡信息的日历数据')
				console.log(this.allDates)
				this.getWeekDates()
			},

			getWeekDates(date = dayJs()) {
				this.curWeekDates = []
				// 克隆日期对象避免污染
				const baseDate = dayJs(date)
				// 获取周起始日
				const startOfWeek = baseDate.startOf('week')
				// 生成周数据
				let weekData = Array.from({
					length: 7
				}).map((_, index) =>
					startOfWeek.add(index, 'day')
				)
				let formatResult = weekData.map(d => d.format('YYYY-MM-DD'))
				this.allDates.forEach(e => {
					if (!e) return
					const {
						date
					} = e
					const existData = formatResult.includes(date)
					if (existData) {
						this.curWeekDates.push(e)
					}
				})

				console.log('整合后的当前周数据')
				console.log(this.curWeekDates)
				const firstDate = this.curWeekDates[0].date
				console.log('周第一天是周几')
				console.log(dayJs(firstDate).day())
				for (let i = 0; i < dayJs(firstDate).day(); i++) {
					this.curWeekDates.unshift(null)
				}
			},

			// 触发日期
			onDateClick(data) {
				const {
					date
				} = data
				this.activeDate = date
				this.curActiveDateInfo = data
			},

			onExpend() {
				this.isExpend = !this.isExpend
			},

			selectDate() {
				this.datetimePickShow = true
			},

			// 回到今天
			backToToday() {
				this.isCurMonth = true
				this.curDate = dayJs().format('YYYY-MM')
				this.activeDate = dayJs().format('YYYY-MM-DD')
				this.datePickerValue = dayJs(dayJs().format('YYYY-MM')).valueOf()
				this.$refs.datePickerRef.innerValue = this.datePickerValue
				this.$emit('date:update', this.curDate)
				// this.initCalendar()
			},

			// 查看打卡记录
			onViewMore() {
				this.$utils.navigateToPage('/pagesClockIn/record')
			},

			onDatetimePickerCancel() {
				this.datetimePickShow = false
			},

			onDatetimePickerConfirm(data) {
				console.log('日期')
				console.log(data)
				const {
					value
				} = data
				this.curDate = dayJs(value).format('YYYY-MM')
				const month = dayJs(value).month() + 1
				const curMonth = dayJs().month() + 1
				if (month < curMonth) {
					this.activeDate = this.curDate + '-01'
					this.isCurMonth = false
				} else {
					if (month === curMonth) {
						this.isCurMonth = true
						// 切换到当月，则设置当天日期为激活日期
						this.activeDate = dayJs().format('YYYY-MM-DD')
					} else {
						this.isCurMonth = false
						// 如果切换到当月后面月份，默认第一天为激活日期
						this.activeDate = this.curDate + '-01'
					}
				}
				// const year = dayJs(value).year()
				// const month = dayJs(value).month() + 1
				this.$emit('date:update', this.curDate)
				// this.initCalendar(year, month)
				this.onDatetimePickerCancel()
				this.isExpend = true
			},

			onModalConfirm() {
				this.modalConfig.show = false
			},

			// 打卡/补卡
			async onToClockIn() {
				const tmplIds = await getCurrentTemplateSubscribe()
				if (tmplIds && tmplIds.length) {
					wx.requestSubscribeMessage({
						tmplIds,
						success: async function(res) {
							if (res.errMsg === 'requestSubscribeMessage:ok') {
								await wx_template_subscribe({
									items: tmplIds.map(wx_template_id => ({
										wx_template_id
									}))
								})
							} else {
								console.log(res.errMsg)
							}
						},
						fail: function(res) {
							console.log(res)
						}
					})
				}
				if (this.clockInBtnDisabled) return
				if (this.clockInBtnText === '补卡' && this.clockInDetail.clockin_data.left_num === 0) {
					// 如果无补卡机会，则提示用户
					if (this.clockInDetail.clockin_data.re_num_limit < this.clockInRuleData.max_renum) {
						this.modalConfig.show = true
					}
					return
				}
				const {
					date
				} = this.curActiveDateInfo
				let reclock_date = this.clockInBtnText === '补卡' ? date : ''
				this.$utils.navigateToPage('/pagesClockIn/clockInForm', `reclock_date=${reclock_date}`)
			}
		}
	}
</script>

<style lang="scss" scoped>
	.calendar-wrap {
		width: 95%;
		padding: 0 26rpx;
		padding-top: 0;
		margin: 30rpx auto 0;
		background: #FFF;
		border-radius: 20rpx;
		box-shadow: 0 2rpx 6rpx 0 rgba(0, 0, 0, 0.05);

		.header {
			// height: 40px;
			@include flex-between;
			padding: 20rpx 0 40rpx;

			.left-wrap {
				@include flex-column-center;
				gap: 20rpx;

				.back-to-today {
					font-size: 24rpx;
					color: #919191;
				}
			}

			.cur-date {
				font-size: 28rpx;
				font-weight: bolder;
			}

			.more-btn {
				@include flex-column-center;

				.btn-text {
					color: #919191;
					font-size: 24rpx;
				}
			}
		}

		.calendar-container {
			.week-row {
				@include flex-column-center;

				.week {
					width: calc(100% / 7);
					height: 60rpx;
					@include flex-center;
					font-size: 28rpx;
					font-weight: bold;
				}
			}

			.date-wrap {
				@include flex-column-center;
				flex-wrap: wrap;
				overflow: hidden;

				.date-item {
					position: relative;
					width: calc(100% / 7);
					height: 70rpx;
					@include flex-center;
					flex-flow: column;

					.date-value {
						width: 40rpx;
						height: 40rpx;
						font-size: 24rpx;
						font-weight: bold;
						border-radius: 50%;
						@include flex-center;

						&_clockin {
							background-color: $clockin-color;
						}

						&_reclockin {
							background-color: $reclockin-color;
						}

						&_active {
							color: #0bb596;
							background-color: $theme-color !important;
						}
					}

					.clockin-tag {
						width: 10rpx;
						height: 10rpx;
						margin-top: 10rpx;
						border-radius: 50%;
						background-color: $clockin-color;
						position: absolute;
						bottom: 0;
						left: 50%;
						transform: translateX(-50%);
					}

					.reclockin-tag {
						background-color: $reclockin-color;
					}
				}
			}

			.expend-btn {
				width: 100%;
				@include flex-column-center;
				gap: 10rpx;

				.line {
					flex: 1;
					transform: scaleY(0.5);
					border-bottom: 1px solid #e6e6e6;
				}
			}

			.clock-in-btn-wrap {
				@include flex-center;
				flex-flow: column;
				gap: 30rpx;
				margin: 60rpx 0 62rpx;

				.btn {
					width: 158rpx;
					height: 158rpx;
					border-radius: 50%;
					background-color: $theme-color;
					@include flex-center;
					font-size: 38rpx;
					font-weight: bolder;

					&-disabled {
						background-color: #e6e6e6;
					}

					&:active {
						opacity: 0.5;
					}
				}

				.info-wrap {
					display: flex;
					gap: 28rpx;

					.count {
						font-size: 24rpx;

						text {
							color: $theme-color;
						}
					}

					.coin-getted-count {
						font-size: 24rpx;
						color: #929292;
						gap: 10rpx;
						@include flex-column-center;
					}
				}
			}
		}
	}
</style>